package com.weizhi.file.controller.admin;

import com.alibaba.fastjson.JSONObject;
import com.github.pagehelper.PageInfo;
import com.github.pagehelper.util.StringUtil;
import com.weizhi.server.dto.FileDto;
import com.weizhi.server.dto.ResponseDto;
import com.weizhi.server.entity.Chapter;
import com.weizhi.server.service.FileService;
import com.weizhi.server.util.Base64ToMultipartFile;
import com.weizhi.server.util.JsonUtil;
import com.weizhi.server.util.PropertyCopyUtil;
import com.weizhi.server.util.UuidUtil;
import lombok.Cleanup;
import lombok.SneakyThrows;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.util.UUID;

@RestController
@RequestMapping("/admin/file")
public class FileController {

    @Autowired
    private FileService fileService;
    @Value("${staticUrl}")
    private String staticUrl;

    @Value("${staticDir}")
    private String staticDir;

    @Value("${oss.domain}")
    private String ossDomain;
    
    private final static Logger logger = LoggerFactory.getLogger(FileController.class);

    @SneakyThrows
    @RequestMapping("/upload/{dir1}/{dir2}")
    public ResponseDto upload(@RequestBody FileDto fileDto, @PathVariable("dir1") String dir1,
                            @PathVariable("dir2") String dir2){

        logger.info("fileController-upload, fileName={}, shareKey={}", fileDto.getName(), fileDto.getShareKey());
        logger.info("file={}", fileDto.getFile());
        String originalFilename = fileDto.getName();
        Integer shareIndex = fileDto.getShareIndex();
        Integer shareTotal = fileDto.getShareTotal();
        String fileBase64 = fileDto.getFile();



        //获取文件存放目录
        String fileSaveDir = staticDir + dir1 + "/" + dir2 + "/";
        File saveFile = new File(fileSaveDir);
        if(!saveFile.exists()) saveFile.mkdirs();
        //获取文件保存名称
//        String key = UuidUtil.getShortUuid();
        String fileSaveName = fileDto.getShareKey() + "." + fileDto.getSuffix();
        String fileShareSaveName = shareTotal <= 1 ? fileSaveName : fileSaveName + "." + fileDto.getShareIndex();

        //保存文件
        saveFile = new File(fileSaveDir, fileShareSaveName);
        MultipartFile file = Base64ToMultipartFile.base64ToMultipart(fileBase64);
        file.transferTo(saveFile);

        //返回文件对象
        fileDto.setPath(dir1 + "/" + dir2 + "/" + fileSaveName);

        //文件合并
        if(shareTotal > 1 && shareIndex == fileDto.getShareTotal()){
            this.merge(fileDto);
            System.gc();
            this.deleteShare(fileDto);
        }

        //保存文件到数据库
        fileService.save(fileDto);

        fileDto.setPath(staticUrl + fileDto.getPath());
        return ResponseDto.createBySuccess(fileDto);
    }

    @SneakyThrows
    public void merge(FileDto fileDto){
        logger.info("UploadController-merge, fileName={}", fileDto.getPath());
        File file = new File(staticDir + fileDto.getPath());
        int shareTotal = fileDto.getShareTotal();
        @Cleanup
        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(file, true));
        byte[] bytes = new byte[1 * 1024 * 1024];
        int len;
        for (int i = 0; i < shareTotal; i++) {
            String fisPath =staticDir + fileDto.getPath() + "." + (i + 1);
            @Cleanup
            BufferedInputStream bis = new BufferedInputStream(new FileInputStream(fisPath));
            while((len = bis.read(bytes, 0, bytes.length)) != -1){
                bos.write(bytes, 0, len);
                bos.flush();
            }

        }

    }

    public void deleteShare(FileDto fileDto){
        for (int i = 0; i < fileDto.getShareTotal(); i++) {
            String path =staticDir + fileDto.getPath() + "." + (i + 1);
            File file = new File(path);
            boolean boo = file.delete();
            logger.info("文件{}删除{}", fileDto.getPath(), boo ? "成功" : "失败");
        }
    }


    @RequestMapping("/check/{key}")
    public ResponseDto check(@PathVariable("key") String shareKey) {
        logger.info("teacherController-list, shareKey={}", shareKey);
        FileDto fileDto = fileService.check(shareKey);
        if(fileDto != null) fileDto.setPath(ossDomain + fileDto.getPath());
        return ResponseDto.createBySuccess(fileDto);
    }

    @RequestMapping("list")
    public ResponseDto list(HttpServletRequest req) {
        JSONObject param = JsonUtil.convertRequest(req);
        logger.info("teacherController-list, param={}", param);
        PageInfo pageInfo = fileService.list(param);
        return ResponseDto.createBySuccess(pageInfo);
    }

    public static void main(String[] args) {
        Chapter f = null;
        FileDto fileDto = PropertyCopyUtil.copy(f, FileDto.class);
        System.out.println(fileDto);
    }


}
